package middleware

import (
	"fmt"
	"net/http"

	"gitee.com/ChangPaoZhe/devops/apps/token"
	"gitee.com/ChangPaoZhe/devops/apps/token/impl"
	"gitee.com/ChangPaoZhe/devops/apps/user"
	"gitee.com/ChangPaoZhe/devops/httpresponse"
	"gitee.com/ChangPaoZhe/devops/ioc"
	"github.com/gin-gonic/gin"
	"github.com/rs/zerolog"
)



type TokenAuther  struct {
	// 调用token接口
	tk  token.Tokener
	// 鉴权，用于确认用户权限
	role user.Role 
	logger  zerolog.Logger

}



func NewTokenAuther() *TokenAuther {
	return &TokenAuther{
		// token 断言
		tk: ioc.GetServer(token.App_Name).(token.Tokener),
	}
}


func (a  *TokenAuther) Auth(c *gin.Context)  {
	at,err:=c.Cookie(token.TOKEN_Cookie_NAME)
	if err!=nil {
		if err == http.ErrNoCookie {
			fmt.Printf("http.ErrNoCookie  token not found  %s\n",err.Error())
			httpresponse.Failed(c,fmt.Errorf("token not found  %s",err.Error()))
			return
		}
		httpresponse.Failed(c, err)
	}
	// 调用模块进行验证
	in:=impl.NewDefaultRequestValidateToken()
	in.Accesstoken=at
	tk,err:=a.tk.ValidateToken(c.Request.Context(), in)
	if err!=nil {
		httpresponse.Failed(c, err)
	}
	if c.Keys== nil {
		c.Keys=map[string]any{}
	}
	c.Keys[token.TOKEN_GIN_KEY_NAME]=tk
}

// 权限鉴定, 鉴权是在用户已经认证的情况之下进行的
// 判断当前用户的角色
func (a *TokenAuther) Perm(c *gin.Context) {
	tkObj := c.Keys[token.TOKEN_GIN_KEY_NAME]
	if tkObj == nil {
		httpresponse.Failed(c, httpresponse.NewPermissionDeny("token not found"))
		return
	}

	tk, ok := tkObj.(*token.Token)
	if !ok {
		httpresponse.Failed(c,httpresponse.NewPermissionDeny("token not an *token.Token"))
		return
	}
	// 如果是Admin则直接放行
	if tk.Role == user.Role_ADMIN {
		return
	}

	if tk.Role !=  a.role{
		httpresponse.Failed(c, httpresponse.NewPermissionDeny("role %d not allow", tk.Role))
		return
	}
}


// 写带参数的 Gin中间件
func Required(r user.Role) gin.HandlerFunc {
	a := NewTokenAuther()
	a.role = r
	return a.Perm
}